/*
 * @Author: your name
 * @Date: 2021-07-08 15:11:00
 * @LastEditTime: 2022-08-08 09:59:03
 * @LastEditors: Please set LastEditors
 * @Description: In User Settings Edit
 * @FilePath: \central-system\src\permission.js
 */
import router from './router'
import NProgress from 'nprogress' // progress bar
import 'nprogress/nprogress.css' // progress bar style
import store from '@/store'
import { localRoute, mainApp, subApp } from '@/config'
import { PERMISSIONS, BEHAVIOR_ANALYSIS } from '@/store/Getter/getterTypes'
import { UPDATE_PERMISSION_QUEUE } from '@/store/Mutation/mutationTypes'
import { PERMISSION } from '@/store/State/stateTypes'
import { GET_PERMISSIONS } from '@/store/Action/actionTypes'
import { getDate, getTitle } from '@/utils/monitor'
import { addMonitor } from '@/api/app'
import storage from '@/utils/storage'
import { Toast } from 'fawkes-mobile-lib'
import Vue from 'vue'

import { GuardsList } from './routerGuards'


NProgress.configure({ showSpinner: false }) // NProgress Configuration
function removeLoading () {
    let loading = document.getElementById('main-loading')
    loading && loading.parentNode.removeChild(loading)
}

let guardsList = new GuardsList()

router.beforeEach(async (to, from, next) => {
    // start progress bar
    NProgress.start()

    let modeName = 'normal'

    switch (true) {
        case Vue.prototype.$InQianKun: {
            modeName = 'inqiankun'
            break
        }
        case subApp: {
            modeName = 'subapp'
            break
        }
        case mainApp: {
            modeName = 'mainapp'
            break
        }

        default:
    }
    let Guards = guardsList.getGuard(modeName, to, from, next)


    if (!Guards.routeRedirect()) {
        Guards.routeResolve()
    }
})

router.beforeResolve(async (to, from, next) => {
    if (localRoute || !to.meta || !to.meta.menuId || store.state[PERMISSION][to.meta.menuId]) {
        next()
        return false
    }
    //获取按钮权限
    await store.dispatch(GET_PERMISSIONS, to.meta.menuId)
    next()
})

router.afterEach((to, from) => {
    let prefix = Vue.prototype.$appBasePath

    if (to.path == prefix + '/distribute') {
        router.replace(prefix + '/home')  //多门户首页重复切换报错解决方案
    }

    let redirect = storage.get('redirectUrl')

    if (redirect == to.fullPath) {
        storage.remove('redirectUrl')
    }

    if (store.getters[BEHAVIOR_ANALYSIS] && storage.get('access_token')) {
        if (from?.name && to?.name) {
            addMonitor({
                ev: 'click',//点击事件
                fun: '页面切换',
                mc: to.name,//模块编码
                mn: getTitle(to.name) || to.name,//模块名称
                pa: to.fullPath,//当前页面路由路径
                fpa: from.fullPath,//前置页面路由路径
                fc: from.name,//前置页面模块编码
                fn: getTitle(from.name) || from.name,//前置页面模块名称
                dur: getDate(storage.get('enterTime'), new Date()),//前置页面停留时间
                url: document.location.href,//当前url地址
                sr: `${window.screen.height}x${window.screen.width}`,//屏幕分辨率
                nt: navigator?.connection?.effectiveType,//网络类型
                fl: store.getters.language || '',//当前系统语言
                lan: navigator.language, //浏览器语言
                depthId: storage.get('depthId')//用户访问深度ID
            })
        }
        if (to?.name) {
            storage.set('enterTime', new Date())
        }
    }
    // finish progress bar
    NProgress.done()
    removeLoading()
})

router.onError((error) => {
    Toast.error('加载的页面发生异常')

    console.error(error)
    NProgress.done()
    removeLoading()
})

export default router

/**
 * @description: 通过code查询用户权限是否已授权
 * @param {String} code 权限编码
 * @param {Object} params 鉴权参数  {Boolean} notFlag 反查标识 | {Array} types 作用门户等级 | {Boolean} entire 全量
 * @return: Boolean
 */
export function nodePermission (codes = [], params = {}) {
    //子应用适配
    let currentStore = Vue.prototype.$InQianKun ? Vue.prototype.$fksMainStore : store
    if (!currentStore) return false

    if (params?.types && currentStore.getters.multiPortal && !params.types.find(type => type == currentStore.state.portal.type)) {
        return true
    }

    let checkCode = (attr) => {
        return currentStore.getters[PERMISSIONS].find(function (item) {
            return attr && attr == item.code
        })
    }

    let findValue

    if (codes instanceof Array) {
        if (params?.entire) {
            findValue = codes.every(code => {
                return code && checkCode(code)
            })
        }
        else {
            findValue = codes.some(code => {
                return code && checkCode(code)
            })
        }
    } else {
        findValue = checkCode(codes)
    }

    checkCode = null

    const rvalue = !!findValue
    return localRoute ? true : (params?.notFlag ? !rvalue : rvalue)
}

export const dataPermission = (code, types) => {
    //子应用适配
    let currentStore = Vue.prototype.$InQianKun ? Vue.prototype.$fksMainStore : store
    if (!currentStore) {
        return false
    }

    if (types && currentStore.getters.multiPortal && !types.find(type => type == currentStore.state.portal.type)) {
        return true
    }

    let has = currentStore.getters[PERMISSIONS].find(p => p.code == code)
    has && currentStore.commit(UPDATE_PERMISSION_QUEUE, has)
    return !!has
}

export const redirectTo = (url) => {
    let to = '/home'
    if (url) {
        to = url
    }
    if (storage.get('redirect') == 1) {
        to = storage.get('redirectUrl') ? storage.get('redirectUrl') : '/home'
        storage.remove('redirect')
    }
    location.replace(location.href.replace(router.currentRoute.path, to))
}
